/* 
 * File:   V4LInterface.cpp
 * Author: gustavo
 * 
 * Created on August 30, 2012, 5:13 AM
 */


#include <iostream>
#include <gtkmm/spinbutton.h>

#include "v4l_interface.hpp"
#include "v4l_interface_events.hpp"

#define DEFAULT_STR " - "

namespace imp {
	namespace gui {
		
		capture::V4LCapture& V4LInterface::get_v4l_capture() {
			return v4lcap;
		}

		void V4LInterface::__init_combo_boxes() {

			ls_input = Gtk::ListStore::create(model_input);
			cb_input.set_model(ls_input);
			cb_input.pack_start(model_input.m_col_name);

			ls_standard = Gtk::ListStore::create(model_standard);
			cb_standard.set_model(ls_standard);
			cb_standard.pack_start(model_standard.m_col_name);

			ls_format_desc = Gtk::ListStore::create(model_format_desc);
			cb_format_desc.set_model(ls_format_desc);
			cb_format_desc.pack_start(model_format_desc.m_col_name);

			ls_frmsize = Gtk::ListStore::create(model_frame_size);
			cb_frame_size.set_model(ls_frmsize);
			cb_frame_size.pack_start(model_frame_size.m_col_name);

		}

		void V4LInterface::__frame_device_conf() {

			Gtk::HBox * hbox;
			Gtk::VBox * vbox;
			Gtk::Label * label;
			Gtk::Table * table;

			frm_device_info.set_label("Device Information");

			vbox = new Gtk::VBox();
			frm_device_info.add(*vbox);

			hbox = new Gtk::HBox();
			vbox->pack_start(*hbox, false, true, 0);


			label = new Gtk::Label("Device: ");
			label->set_alignment(1.0, .5);
			hbox->pack_start(*label, false, true, 0);

			hbox->pack_start(cb_device, true, true, 0);

			bt_start.set_label("start");
			hbox->pack_start(bt_start, false, true, 0);

			hbox = new Gtk::HBox();
			vbox->pack_start(*hbox, false, true, 0);

			table = new Gtk::Table(2, 4, false);

			lb_device_name.set_text(DEFAULT_STR);
			lb_device_driver.set_text(DEFAULT_STR);
			lb_device_card.set_text(DEFAULT_STR);
			lb_device_bus.set_text(DEFAULT_STR);

			label = new Gtk::Label("Device: ");
			label->set_alignment(1.0, .5);
			table->attach(*label, 0, 1, 0, 1);
			lb_device_name.set_alignment(0, .5);
			table->attach(lb_device_name, 1, 2, 0, 1);

			label = new Gtk::Label("Card: ");
			label->set_alignment(1.0, .5);
			table->attach(*label, 0, 1, 1, 2);
			lb_device_card.set_alignment(0, .5);
			table->attach(lb_device_card, 1, 2, 1, 2);

			label = new Gtk::Label("Driver: ");
			label->set_alignment(1.0, .5);
			table->attach(*label, 2, 3, 0, 1);
			lb_device_driver.set_alignment(0, .5);
			table->attach(lb_device_driver, 3, 4, 0, 1);

			label = new Gtk::Label("Bus: ");
			label->set_alignment(1.0, .5);
			table->attach(*label, 2, 3, 1, 2);
			lb_device_bus.set_alignment(0, .5);
			table->attach(lb_device_bus, 3, 4, 1, 2);

			hbox->pack_start(*table, true, true, 0);

		}

		void V4LInterface::__frame_device_prop() {

			Gtk::HBox * hbox;
			Gtk::VBox * vbox;
			Gtk::Label * label;
			Gtk::Table * table;

			table = new Gtk::Table(4, 4, false);

			label = new Gtk::Label("input: ");
			label->set_alignment(1, .5);
			table->attach(*label, 0, 1, 0, 1, Gtk::FILL, Gtk::SHRINK, 0, 0);
			table->attach(cb_input, 1, 2, 0, 1, Gtk::FILL, Gtk::SHRINK, 0, 0);

			label = new Gtk::Label("standard: ");
			label->set_alignment(1, .5);
			table->attach(*label, 3, 4, 0, 1, Gtk::FILL, Gtk::SHRINK, 0, 0);
			table->attach(cb_standard, 5, 6, 0, 1, Gtk::FILL, Gtk::SHRINK, 0, 0);

			label = new Gtk::Label("format: ");
			label->set_alignment(1, .5);
			table->attach(*label, 0, 1, 1, 2, Gtk::FILL, Gtk::SHRINK, 0, 0);
			table->attach(cb_format_desc, 1, 2, 1, 2, Gtk::FILL, Gtk::SHRINK, 0, 0);

			label = new Gtk::Label("frame size: ");
			label->set_alignment(1, .5);
			table->attach(*label, 3, 4, 1, 2, Gtk::FILL, Gtk::SHRINK, 0, 0);
			table->attach(cb_frame_size, 5, 6, 1, 2, Gtk::FILL, Gtk::SHRINK, 0, 0);


			label = new Gtk::Label("frame width: ");
			label->set_alignment(1, .5);
			table->attach(*label, 0, 1, 3, 4, Gtk::FILL, Gtk::SHRINK, 0, 0);
			table->attach(sp_width, 1, 2, 3, 4, Gtk::FILL, Gtk::SHRINK, 0, 0);

			label = new Gtk::Label("frame height: ");
			label->set_alignment(1, .5);
			table->attach(*label, 3, 4, 3, 4, Gtk::FILL, Gtk::SHRINK, 0, 0);
			table->attach(sp_height, 5, 6, 3, 4, Gtk::FILL, Gtk::SHRINK, 0, 0);

			notebook.append_page(*table, "Properties");

			frm_device_prop.add(notebook);



		}

		void V4LInterface::__connect_signals() {

			cb_device.signal_changed().connect(sigc::mem_fun(*this, &V4LInterface::event_cb_device_changed));
			bt_start.signal_clicked().connect(sigc::mem_fun(*this, &V4LInterface::event_bt_start_clicked));


			cb_input_signal = cb_input.signal_changed().connect(sigc::mem_fun(*this, &V4LInterface::event_cb_input_changed));
			cb_standard_signal = cb_standard.signal_changed().connect(sigc::mem_fun(*this, &V4LInterface::event_cb_standard_changed));
			cb_format_desc_signal = cb_format_desc.signal_changed().connect(sigc::mem_fun(*this, &V4LInterface::event_cb_format_desc_changed));
			cb_frmsize_signal = cb_frame_size.signal_changed().connect(sigc::mem_fun(*this, &V4LInterface::event_cb_frame_size_changed));


		}

		V4LInterface::V4LInterface() : Gtk::VBox(false, 2) {

			sp_width.set_range(0, 2000);
			sp_width.set_increments(1, 10);
			sp_height.set_range(0, 2000);
			sp_height.set_increments(1, 10);

			__init_combo_boxes();

			__frame_device_conf();
			this->pack_start(frm_device_info, false, true, 0);

			__frame_device_prop();
			this->pack_start(frm_device_prop, false, true, 0);

			char * dev_name = NULL;
			int init = 1;
			while (v4l_enum_devices(&dev_name, init, 20)) {
				init = 0;
				cb_device.append(dev_name);
			}

			__connect_signals();

			this->show();

		}

		V4LInterface::~V4LInterface() {

			ls_input->clear();
			ls_standard->clear();
			ls_format_desc->clear();
			ls_frmsize->clear();

			ctrl_list_default.clear();
			ctrl_list_user.clear();
			ctrl_list_private.clear();

		}

	}
}

